package jtt809.handler;

import com.sjx.jtt809.pojo.Response;
import cn.hutool.core.thread.ThreadUtil;
import cn.hutool.json.JSONUtil;
import cn.hutool.log.Log;
import cn.hutool.log.LogFactory;
import io.netty.channel.ChannelHandlerContext;
import io.netty.channel.EventLoop;
import io.netty.channel.SimpleChannelInboundHandler;
import io.netty.handler.timeout.IdleState;
import io.netty.handler.timeout.IdleStateEvent;
import jtt809.PrimaryLinkClientManager;
import jtt809.business.ClientBusinessFactory;
import jtt809.pojo.RequestClientJtt809_0x1005;
import jtt809.pojo.ResponseClientJtt809_0x1002;

import java.util.concurrent.TimeUnit;

/**
 * 主链路处理器
 */
public class PrimaryLinkClientJtt809Handler extends SimpleChannelInboundHandler<Response> {

    private static final Log logger = LogFactory.get();

    private String ip;

    private int port;

    private String downLinkIp;

    private int downLinkPort;

    private PrimaryLinkClientManager primaryLinkClient;

    public String getIp() {
        return ip;
    }

    public void setIp(String ip) {
        this.ip = ip;
    }

    public int getPort() {
        return port;
    }

    public void setPort(int port) {
        this.port = port;
    }

    public String getDownLinkIp() {
        return downLinkIp;
    }

    public void setDownLinkIp(String downLinkIp) {
        this.downLinkIp = downLinkIp;
    }

    public int getDownLinkPort() {
        return downLinkPort;
    }

    public void setDownLinkPort(int downLinkPort) {
        this.downLinkPort = downLinkPort;
    }

    public PrimaryLinkClientJtt809Handler(String ip, int port, String downLinkIp, int downLinkPort) {
        this.ip = ip;
        this.port = port;
        this.downLinkIp = downLinkIp;
        this.downLinkPort = downLinkPort;
        this.primaryLinkClient = new PrimaryLinkClientManager(ip, port, downLinkIp, downLinkPort);
    }

    @Override
    protected void channelRead0(ChannelHandlerContext ctx, Response msg) throws Exception {
        // 收到消息直接打印输出
        logger.info("=====> 【下级平台|接收】指令 = {} ， 数据 = {}", Integer.toHexString(msg.getMsgId()), JSONUtil.toJsonStr(msg));

        // 开启线程执行业务方法
        ThreadUtil.execute(new ClientBusinessFactory(ctx, msg));
    }

    @Override
    public void channelActive(ChannelHandlerContext ctx) throws Exception {
        super.channelActive(ctx);
    }

    @Override
    public void channelInactive(ChannelHandlerContext ctx) throws Exception {
        logger.info("======> 【下级平台|信息】与上级平台服务端失去连接！");

        // 使用过程中断线重连
        final EventLoop eventLoop = ctx.channel().eventLoop();
        eventLoop.schedule(new Runnable() {
            public void run() {
                primaryLinkClient.start();
            }
        }, 1, TimeUnit.SECONDS);
        ctx.fireChannelInactive();
    }

    @Override
    public void userEventTriggered(ChannelHandlerContext ctx, Object evt) throws Exception {
        if (evt instanceof IdleStateEvent) {
            IdleStateEvent event = (IdleStateEvent) evt;
            if (event.state().equals(IdleState.READER_IDLE)) {
                logger.info("======> 【下级平台|信息】长时间没收到上级平台推送的数据");
                // 超时关闭channel
                // ctx.close();
            } else if (event.state().equals(IdleState.WRITER_IDLE)) {
                // 上级平台登录成功，则发送心跳,保持长连接
                if (ResponseClientJtt809_0x1002.isIsLoginFlagFromUpPlatform()) {
                    ctx.channel().writeAndFlush(new RequestClientJtt809_0x1005());
                    logger.info("======> 【下级平台|信息】心跳发送成功!");
                } else {
                    logger.info("======> 【下级平台|信息】上级平台登录失败，不发送心跳!");
                }
            } else if (event.state().equals(IdleState.ALL_IDLE)) {
                logger.info("======> 【下级平台|信息】ALL_IDLE");
            }
        }
        super.userEventTriggered(ctx, evt);
    }
}